Skip to content

ci: run the HTTP and TCP test suites only for the changes that affect them - #634

Merged
alex-clickhouse merged 4 commits into
mainfrom
alex-clickhouse/ci-transport-path-filters
Sep 29, 2026
Merged

alex-clickhouse merged 4 commits into
mainfrom
alex-clickhouse/ci-transport-path-filters

Conversation

@alex-clickhouse

@alex-clickhouse alex-clickhouse commented Sep 28, 2026 •

Copy link
Copy Markdown
Collaborator

Why

tests.yml ran the whole HTTP suite (14 jobs) on every pull request, including TCP-only, docs-only and workflow-only changes. tests-tcp.yml was already path-filtered, but its filters did not include ClickHouse.Driver.Common, which both TCP projects reference, so a change to the shared code ran only the HTTP suite.

Only the HTTP suite uploaded coverage. A TCP pull request got no coverage gate, and the Codecov total did not include the TCP driver.

What changed

  • tests.yml (HTTP): an allowlist paths filter on push and pull_request.
  • tests-tcp.yml (TCP): adds ClickHouse.Driver.Common/**, the shared build inputs, codecov.yml and !**/*.md to the existing filter, and two new jobs: HTTP driver build (TCP) (see the first note) and Code Coverage (TCP) (see Coverage).
  • reusable-tcp.yml, reusable.yml: a coverage input and a Codecov upload with the flag tcp, and the flag http on the existing HTTP upload. Neither uploads for an explicit ref.
  • codecov.yml: both flags carry forward.
  • ClickHouse.Driver.Tcp.Tests.csproj: does not instrument ClickHouse.Driver.Common/Vendor, the same as the HTTP test project. codecov.yml already ignores it.
  • CONTRIBUTING.md: the TCP coverage command, and the coverage rules that CI applies.
  • examples.yml: adds the shared build inputs and !**/*.md.
  • codeql.yml, benchmark.yml (push to main only): add docs/** to paths-ignore. The docs are .mdx files, so **/*.md did not match them.

Which workflows run on a pull request into main

The change touches HTTP TCP Examples
ClickHouse.Driver/** ✓ ✓
ClickHouse.Driver.Tests/**, ClickHouse.Driver.IntegrationTests/** ✓
ClickHouse.Driver.Tcp/** ✓ ✓
ClickHouse.Driver.Tcp.Tests/** ✓
ClickHouse.Driver.Common/** ✓ ✓ ✓
Shared build inputs (below) ✓ ✓ ✓
codecov.yml ✓ ✓
examples/** ✓
tests.yml, reusable.yml, tests-integration.yml, tests-cloud.yml, tests-windows.yml, tests-macos.yml ✓
tests-tcp.yml, reusable-tcp.yml, tests-cloud-tcp.yml ✓
examples.yml ✓
Only docs/**, *.md, changelog.d/**, ClickHouse.Driver.Benchmark/**, other workflows, .claude/, .agents/

The shared build inputs, the same in all three workflows:

  • Directory.Packages.props sets the package versions for every project. Six packages are used only by the examples (Polly, the OpenTelemetry console exporter, and some Microsoft.Extensions packages).
  • Directory.Build.*, global.json and [Nn]u[Gg]et.[Cc]onfig do not exist yet. MSBuild, the SDK and NuGet read them from the repository root, so they are listed before they exist: a pull request that adds one runs all three workflows.
  • .editorconfig holds the analyzer and code-style settings. The three library projects set EnforceCodeStyleInBuild.
  • sgKey.snk is the strong-name key of the two drivers, Common and both unit test projects. The InternalsVisibleTo attributes carry its public key.

codecov.yml configures Codecov for both coverage uploads, so a change to it runs both suites.

Coverage

Before After
Uploads HTTP suite, no flag HTTP suite, flag http; TCP suite, flag tcp
Gate on a pull request codecov/patch 75%, HTTP report only codecov/patch 75%, reports of the suites that ran
Total of a main commit HTTP driver and Common HTTP driver, TCP driver and Common
  • Pull requests. Each suite that runs uploads its report, and codecov/patch uses those reports. A TCP-only pull request is gated on the TCP report.
  • main. With the path filters, a push to main can run only one suite. Carryforward copies the report of the other flag from the nearest earlier commit that has one, so the total of each commit covers both drivers. A suite that did not run had no input change, so its carried-forward report is still correct.
  • Transition. The commits on main before this merge have one upload with no flag. This pull request changes the workflows of both suites, so its merge commit uploads both flags. A pull request based on an older commit has no http report to carry forward, so its Codecov total is TCP only until it is rebased. codecov/patch is not affected.
  • Manual runs with a ref. Codecov records an upload for the commit that started the workflow, not for the ref that the job checks out. With an explicit ref, the coverage jobs of both suites run the tests but do not upload.
  • The project total is measured, not gated. codecov.yml configures a project status, but Codecov posts no codecov/project check on this repository. No pull request or main commit that I checked has one, and the Codecov PR comments use the Team plan format, which has no project coverage.

Notes

  • TCP-only changes skip the HTTP suite, but not the HTTP driver build. ClickHouse.Driver references ClickHouse.Driver.Tcp (net8.0 and later) to pack the TCP assembly into the NuGet package, so it compiles against the TCP public types. No HTTP code or test uses them. But a public TCP type can collide with a type that ClickHouse.Driver sees, possibly on some target frameworks only, and examples.yml builds net10.0 only. The new HTTP driver build (TCP) job builds ClickHouse.Driver for all four target frameworks, without the package, whenever the TCP workflow runs. It needs no ClickHouse server.
  • Benchmark-only changes run no test suite. No pull request job builds ClickHouse.Driver.Benchmark, with or without this change. The HTTP suite does not reference it.
  • No required checks are affected. main has no required status checks (the rulesets require one approval), so a workflow that a path filter skips cannot block a merge. If a suite becomes a required check later, it needs a gate job that always runs, because GitHub leaves the checks of a path-skipped workflow pending.
  • Stacked pull requests into tcp/** keep the current behavior: the TCP workflow runs on them (now including the HTTP driver build and the coverage job, so they get codecov/patch too), and the HTTP suite and the examples run when the pull request targets main. A stacked pull request gets these jobs once its branch contains this change.
  • workflow_dispatch still starts every suite by hand.

Verification

  • Replayed the old and the new filters over the 160 first-parent commits on main since 2026-06-01. Pull requests are squash-merged, so each commit is one pull request. The script reads the on: blocks from both trees and applies the GitHub matching rules (last matching pattern wins, ! excludes):

    Workflow Old New
    HTTP tests, pull_request 160 94
    HTTP tests, push 156 94
    TCP tests, pull_request 47 53
    Examples, pull_request 110 115
    CodeQL and Benchmark, push 156 153

    I checked each commit whose result changed. The 66 removed HTTP runs are 36 TCP code or test changes, 16 changes to non-test workflows or .github configuration, 13 docs, changelog or repository configuration changes, and 1 benchmark change. The 6 added TCP runs are 5 ClickHouse.Driver.Common changes and 1 codecov.yml change (Update codecov.yml #372). The 5 added examples runs are Directory.Packages.props bumps. The 3 removed CodeQL and benchmark runs are docs-only merges.

  • The same script checked 39 example paths against the real filters, including Directory.Build.targets, nuget.config, NuGet.Config, a vendored README.md inside ClickHouse.Driver.Common, and every workflow file of each suite.

  • The open Dependabot pull requests Bump Microsoft.Extensions.Configuration and Microsoft.Extensions.Configuration.Json #378 and Bump Microsoft.Extensions.Diagnostics.HealthChecks from 10.0.8 to 10.0.9 #379 bump packages that only the examples use. The examples workflow did not run on either of them.

  • The HTTP driver build job catches a TCP-only break. On a scratch copy, a public TCP type named ClickHouse.Driver.Compression.PooledWriteBufferStream, compiled for net8.0 and net9.0 only, left the TCP test project build (net9.0) and the examples build green. The job's command failed with CS0433 on net8.0 and net9.0 (BatchWriteTarget.cs uses the internal Common type of that name). On this branch the same command passes for net6.0, net8.0, net9.0 and net10.0, and produces no package.

  • actionlint 1.7.12: the only new finding is one more $/ self-repository reference, for the new coverage job (6 on the previous tip of this branch, 7 now). actionlint does not know that syntax yet. The shellcheck findings are in files this pull request does not change.

  • zizmor 1.29.0 (the gate version) with .github/zizmor.yml: no findings at high, and the same 13 low and 22 medium findings as origin/main with the default persona. The auditor persona adds one low concurrency-limits finding for tests-tcp.yml, which now has a job of its own; ten workflows on main already have the same finding.

  • The command of the new coverage job, run locally (net10.0, latest server, Testcontainers): 4186 tests pass in 2.6 minutes and it writes ClickHouse.Driver.Tcp.Tests/coverage.net10.0.opencover.xml, the file the upload step reads. The report has ClickHouse.Driver.Tcp at 95.0% lines and ClickHouse.Driver.Common at 45.5%, and no vendored files. The HTTP report has Common at 98.4%, and Codecov merges the two.

  • codecov.io/validate accepts the new codecov.yml.

  • This pull request changes the workflow files of all three suites, so its own checks run the new on: blocks and the new jobs, and its merge commit uploads both flags.

🤖 Generated with Claude Code

alex-clickhouse and others added 3 commits September 28, 2026 20:21
tests.yml ran the whole HTTP suite, 14 jobs, on every pull request,
including TCP-only, docs-only and workflow-only changes. tests-tcp.yml
was already path-filtered, but its filters left out
ClickHouse.Driver.Common, which the TCP projects reference, so a Common
change ran only the HTTP suite.

Both suites now use allowlist path filters. ClickHouse.Driver.Common and
the shared build inputs are in both lists: Directory.Packages.props,
Directory.Build.*, global.json, NuGet.config, .editorconfig and
sgKey.snk. Some of these root files do not exist yet; they are listed so
that a pull request that adds one runs both suites. Markdown files do
not run either suite.

ClickHouse.Driver references ClickHouse.Driver.Tcp (net8.0 and later) to
pack the TCP assembly, so it compiles against the TCP public types. No
HTTP code or test uses them, but a public TCP type can still collide
with a type that ClickHouse.Driver sees, possibly on some target
frameworks only. A new job in tests-tcp.yml builds ClickHouse.Driver for
every target framework, so a TCP-only change that breaks the HTTP driver
build still fails a check.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Some packages are used only by the examples project: Polly, the
OpenTelemetry console exporter, and some Microsoft.Extensions packages.
A pull request that changed only their versions in
Directory.Packages.props did not run the examples workflow, so no job
built the one project that uses them.

The workflow now lists the same shared build inputs as tests.yml and
tests-tcp.yml. Markdown files, such as examples/Tcp/README.md, no longer
run it.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The docs are .mdx files, so the existing "**/*.md" ignore did not match
them, and a docs-only merge started a CodeQL analysis and a benchmark
run. Neither reads docs/.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@codecov

codecov Bot commented Sep 28, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

@alex-clickhouse
alex-clickhouse marked this pull request as ready for review September 29, 2026 08:56
Copilot AI balanced review requested due to automatic review settings September 29, 2026 08:56

Copilot AI left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot review overview

🟢 Approval recommended

The filters align with project dependencies, and TCP-only changes retain multi-framework HTTP build validation.

Review effort: Balanced
Findings: None

What changed in this PR

This PR narrows CI execution to relevant project paths while preserving cross-project build validation.

Changes:

  • Adds targeted HTTP, TCP, and examples path filters.
  • Adds an HTTP driver compatibility build to TCP CI.
  • Skips CodeQL and benchmarks for documentation-only changes.
File Description
.github/​workflows/​tests.yml Limits HTTP CI to relevant inputs.
.github/​workflows/​tests-tcp.yml Expands TCP inputs and adds HTTP compatibility build.
.github/​workflows/​examples.yml Covers shared build inputs.
.github/​workflows/​codeql.yml Ignores docs-only pushes.
.github/​workflows/​benchmark.yml Ignores docs-only pushes.

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Only the HTTP Code Coverage job uploaded a report, so a TCP pull
request got no coverage gate and the Codecov total covered only the
HTTP driver and Common.

A new Code Coverage (TCP) job runs the TCP suite on net10.0 with
coverlet and uploads the report with the Codecov flag tcp. The HTTP
upload gets the flag http. Both reports go to the same codecov/patch
status, with the 75% target.

The path filters let a push to main run only one suite. codecov.yml
sets both flags to carry forward, so Codecov copies the missing report
from the nearest earlier commit that has one, and the total of each
commit covers both drivers. codecov.yml is now an input of the TCP
suite too.

Codecov records an upload for the commit that started the workflow,
not for the ref that the job checks out. So neither coverage job
uploads when a manual run gives an explicit ref.

The TCP test project excludes the vendored code in Common/Vendor from
instrumentation, as the HTTP test project does. codecov.yml already
ignores it. CONTRIBUTING.md gets the TCP coverage command and the
coverage rules that CI applies.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@alex-clickhouse
alex-clickhouse enabled auto-merge (squash) September 29, 2026 10:20
@alex-clickhouse
alex-clickhouse merged commit a19025e into main Sep 29, 2026
30 checks passed
@alex-clickhouse
alex-clickhouse deleted the alex-clickhouse/ci-transport-path-filters branch September 29, 2026 11:02
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants